////////////////////////////////////////////////////////////////////////////////
//Define crlf
////////////////////////////////////////////////////////////////////////////////

var crlf            = String.fromCharCode(13, 10);

var notifications   = true;

////////////////////////////////////////////////////////////////////////////////
//Note: For latest displaynames see getTagName() function.
////////////////////////////////////////////////////////////////////////////////

/*
{ -------------------------------------------------
{
{ Takenpaar
{     -Titel/Studielast
{     Theorietaak
{     Vaardigheidstaak.
{
{ -------------------------------------------------
{
{ Theorietaak (eerste tab)
{     -Titel/Studielast
{      Diagnostische TOETS                      (ev)
{      Studeeropdrachten / studeerOPDRACHT      (mv)
{      ZelfTOETS /Items                         (mv)
{     Introductie                               (ev)
{     Leerdoelen / leerdoel...                  (mv)
{     Studeeeraanwijzing                        (ev)
{     Casus(beschrijving)                       (ev)
{     Bronnen / Bron                            (mv)
{     Instrumenten /  Instrument                (mv)
{     Metadata
{
{ Vaardigheidstaak (tweede tab)
{     -Titel/Studielast
{      VoorbeeldOPDRACHT                        (ev)
{      OefenOPDRACHT                            (ev)
{      ToetsOPDRACHT                            (ev)
{     Introductie                               (ev)
{     Leerdoelen / leerdoel...                  (mv)
{     Studeeeraanwijzing                        (ev)
{     Casus(beschrijving)                       (ev)
{     Bronnen / Bron                            (mv)
{     Instrumenten /  Instrument                (mv)
{     Metadata
{
{ -------------------------------------------------
{
{ Opdracht
{     -Titel/Studielast
{     Introductie                               (ev)
{     Studeeeraanwijzing                        (ev)
{     Leerdoelen                                (ev)
{     Casus(beschrijving)                       (ev)
{     Leerkern                                  (meerdere van de volgende 3)
{        Text
{        Vragen
{        Feedback
{     Bronnen / Bron                            (mv)
{     Instrumenten /  Instrument                (mv)
{     Metadata
{
{ -------------------------------------------------
{
{ Toets
{     -Titel/Studielast
{     Introductie                               (ev)
{     Zelftoets                                 (mv, MC)
{        Vragen
{        Feedback
{     Metadata
{
{ -------------------------------------------------
{
{ Diagnostische toets                           (=Toets, MC)
{
{ Zelftoets                                     (=Toets, MC)
{
{ Studeeropdracht                               (=Opdracht, OV)
{
{ Voorbeeldopdracht                             (=Opdracht)
{
{ Oefenopdracht                                 (=Opdracht)
{
{ Toetsopdracht                                 (=Opdracht)
{
{ -------------------------------------------------
*/

////////////////////////////////////////////////////////////////////////////////
//Define Tag Constants.
////////////////////////////////////////////////////////////////////////////////

var tagTheorieTaak         = 001;
var tagVaardigheidsTaak    = 002;

var tagIntakeOpdracht      = 100;
var tagStudeerOpdrachten   = 101;        //Plural
var tagStudeerOpdracht     = 102;
var tagZelftoetsOpdracht   = 103;
var tagVoorbeeldOpdracht   = 104;
var tagOefenOpdracht       = 105;
var tagToetsOpdracht       = 106;
var tagVoorbeeldOpdrachten = 107;        //Plural
var tagOefenOpdrachten     = 108;        //Plural
var tagToetsOpdrachten     = 109;        //Plural
 
var tagIntroductie         = 200;
var tagLeerdoelen          = 201;
var tagStudeeraanwijzingen = 202;
var tagInstrumenten        = 203;
var tagBronnen             = 204;
var tagCasus               = 205;
var tagLeerKern            = 206;
var tagToets               = 207;
var tagToetsOpgaven        = 208;
var tagCriteria            = 209;

var tagMetadata            = 300;

////////////////////////////////////////////////////////////////////////////////
//Converts a Tag Constant into String.
////////////////////////////////////////////////////////////////////////////////

function getTagName(i) {
  switch (i) {
    case tagTheorieTaak: 	        return "Theorietaak";
        case tagIntakeOpdracht:         return "Diagnostische toets";
        case tagStudeerOpdrachten:      return "Studeeropdrachten";
            case tagStudeerOpdracht:    return "Studeeropdracht";
        case tagZelftoetsOpdracht:      return "Zelftoets";

    case tagVaardigheidsTaak: 	        return "Vaardigheidstaak";
        case tagVoorbeeldOpdrachten:    return "Voorbeeldopdrachten";
            case tagVoorbeeldOpdracht:  return "Voorbeeldopdracht";
        case tagOefenOpdrachten:        return "Oefenopdrachten";
            case tagOefenOpdracht:      return "Oefenopdracht";
        case tagToetsOpdrachten:        return "Toetsopdrachten";
            case tagToetsOpdracht:      return "Toetsopdracht";

    case tagIntroductie:                return "Introductie";
    case tagLeerdoelen:		        return "Leerdoelen";
    case tagStudeeraanwijzingen:        return "Studeeraanwijzingen";
    case tagInstrumenten:               return "Instrumenten";
    case tagBronnen:                    return "Bronnen";
    case tagToets:                      return "Toets";
    case tagCasus:                      return "Casus";
    case tagLeerKern:                   return "Opdrachtscenario";
    case tagToetsOpgaven:               return "Toetsvragen";
    case tagCriteria:                   return "Beoordelingscriteria";

    case tagMetadata:                   return "Metadata";
  }
  return "error";
}

////////////////////////////////////////////////////////////////////////////////
//Get the correct structure for a tag passed in.
////////////////////////////////////////////////////////////////////////////////

function getStructure(i) {
  switch (i) {
    case tagTheorieTaak:            return getTheorieTaak();                    //ok
        case tagIntakeOpdracht:     return getToets(i);                         //ok
        case tagStudeerOpdracht:    return getOpdracht(i);                      //ok
        case tagZelftoetsOpdracht:  return getToets(i);                         //ok
    case tagVaardigheidsTaak:       return getVaardigheidsTaak();               //ok
        case tagVoorbeeldOpdracht:  return getOpdracht(i);                      //ok
        case tagOefenOpdracht:      return getOpdracht(i);                      //ok
        case tagToetsOpdracht:      return getOpdracht(i);                      //ok
  }
  return i;
}

////////////////////////////////////////////////////////////////////////////////
//Returns the base structure for a 'TheorieTaak'.
////////////////////////////////////////////////////////////////////////////////

function getTheorieRoot() {
  return ""    +  tagTheorieTaak        + crlf +
          "#"  +  tagIntroductie        + crlf +
          "#"  +  tagLeerdoelen         + crlf +
          "#"  +  tagStudeeraanwijzingen+ crlf +
          "#"  +  tagCasus              + crlf +
          "#"  +  tagBronnen            + crlf +
          "#"  +  tagInstrumenten       + crlf +
//        "#"  +  tagToetsOpgaven       + crlf +
          ""   + _getPrefixToets(tagIntakeOpdracht, "#") + crlf +
          "#"  +  tagStudeerOpdrachten + crlf +
          ""   + _getPrefixOpdracht(tagStudeerOpdracht, "##") + crlf +
          ""   + _getPrefixToets(tagZelftoetsOpdracht, "#") + crlf +
          "#"  +  tagMetadata;
}

////////////////////////////////////////////////////////////////////////////////
//Returns the base structure for a 'VaardigheidsTaak'.
////////////////////////////////////////////////////////////////////////////////

function getVaardigheidsRoot() {
  return ""   +  tagVaardigheidsTaak    + crlf +
          "#"  +  tagIntroductie        + crlf +
          "#"  +  tagLeerdoelen         + crlf +
          "#"  +  tagStudeeraanwijzingen+ crlf +
          "#"  +  tagCasus              + crlf +
          "#"  +  tagBronnen            + crlf +
          "#"  +  tagInstrumenten       + crlf +
          "#"  +  tagVoorbeeldOpdrachten+ crlf +
          ""   +  _getPrefixOpdracht(tagVoorbeeldOpdracht, "##") + crlf +
          "#"  +  tagOefenOpdrachten    + crlf +
          ""   + _getPrefixOpdracht(tagOefenOpdracht, "##") + crlf +
          "#"  +  tagToetsOpdrachten    + crlf +
          ""   + _getPrefixOpdracht(tagToetsOpdracht, "##") + crlf +
          "#"  +  tagMetadata;
}

////////////////////////////////////////////////////////////////////////////////
//Returns a Top Level TheorieTaak.
////////////////////////////////////////////////////////////////////////////////

function getTheorieTaak() {
  return _getPrefixTheorieTaak("");
}

////////////////////////////////////////////////////////////////////////////////
//Returns a TheorieTaak based on a Identing Prefix.
////////////////////////////////////////////////////////////////////////////////

function _getPrefixTheorieTaak(prefix) {
  return prefix + tagIntroductie         + crlf +
         prefix + tagLeerdoelen          + crlf +
         prefix + tagStudeeraanwijzingen + crlf +
         prefix + tagInstrumenten        + crlf +
         prefix + tagBronnen             + crlf +
         prefix + tagCasus               + crlf +
         prefix + tagIntakeOpdracht      + crlf +
         prefix + tagStudeerOpdrachten   + crlf +
         prefix + tagZelftoetsopdracht   + crlf +
         prefix + tagMetadata;
}

////////////////////////////////////////////////////////////////////////////////
//Returns a Top Level VaardigheidsTaak.
////////////////////////////////////////////////////////////////////////////////

function getVaardigheidsTaak() {
  return _getPrefixVaardigheidsTaak("");
}

////////////////////////////////////////////////////////////////////////////////
//Returns a VaardigheidsTaak based on a Identing Prefix.
////////////////////////////////////////////////////////////////////////////////

function _getPrefixVaardigheidsTaak(prefix) {
  return prefix + tagIntroductie         + crlf +
         prefix + tagLeerdoelen          + crlf +
         prefix + tagStudeeraanwijzingen + crlf +
         prefix + tagInstrumenten        + crlf +
         prefix + tagBronnen             + crlf +
         prefix + tagCasus               + crlf +
         prefix + tagVoorbeeldOpdrachten + crlf +
         prefix + tagOefenOpdrachten     + crlf +
         prefix + tagToetsOpdrachten     + crlf +
         prefix + tagMetadata;
}

////////////////////////////////////////////////////////////////////////////////
//Returns a Top Level Opdracht of a certain tag.
////////////////////////////////////////////////////////////////////////////////

function getOpdracht(tag) {
  return _getPrefixOpdracht(tag, "");
}

////////////////////////////////////////////////////////////////////////////////
//Returns a Opdracht based on a Identing Prefix and tag.
////////////////////////////////////////////////////////////////////////////////

function _getPrefixOpdracht(tag, prefix) {
  if (tag == tagStudeerOpdracht) {
  return prefix + ""    + tag                     + crlf +
         prefix +  "#"  + tagIntroductie          + crlf +
         prefix +  "#"  + tagLeerdoelen           + crlf +
         prefix +  "#"  + tagStudeeraanwijzingen  + crlf +
         prefix +  "#"  + tagCasus                + crlf +
         prefix +  "#"  + tagLeerKern             + crlf +
         prefix +  "#"  + tagBronnen              + crlf +
         prefix +  "#"  + tagInstrumenten         + crlf +
         prefix +  "#"  + tagMetadata;
  } else if (tag == tagToetsOpdracht) {
  return prefix + ""    + tag                     + crlf +
         prefix +  "#"  + tagIntroductie          + crlf +
         prefix +  "#"  + tagStudeeraanwijzingen  + crlf +
         prefix +  "#"  + tagCasus                + crlf +
         prefix +  "#"  + tagLeerKern             + crlf +
         prefix +  "#"  + tagBronnen              + crlf +
         prefix +  "#"  + tagInstrumenten         + crlf +
         prefix +  "#"  + tagCriteria             + crlf +
         prefix +  "#"  + tagMetadata;
  } else {
  return prefix + ""    + tag                     + crlf +
         prefix +  "#"  + tagIntroductie          + crlf +
         prefix +  "#"  + tagStudeeraanwijzingen  + crlf +
         prefix +  "#"  + tagCasus                + crlf +
         prefix +  "#"  + tagLeerKern             + crlf +
         prefix +  "#"  + tagBronnen              + crlf +
         prefix +  "#"  + tagInstrumenten         + crlf +
         prefix +  "#"  + tagMetadata;
  }                
}

////////////////////////////////////////////////////////////////////////////////
//Returns a Top Level Toets of a certain tag.
////////////////////////////////////////////////////////////////////////////////

function getToets(tag) {
  return _getPrefixToets(tag,"");
}

////////////////////////////////////////////////////////////////////////////////
//Returns a Toets based on a Identing Prefix and tag.
////////////////////////////////////////////////////////////////////////////////

function _getPrefixToets(tag, prefix) {
  return prefix + ""   + tag                      + crlf +
         prefix +  "#"  + tagIntroductie          + crlf +
         prefix +  "#"  + tagToetsOpgaven         + crlf +
         prefix +  "#"  + tagMetadata;
}

////////////////////////////////////////////////////////////////////////////////
//Returns true if the tag passed can be added in the GUI.
////////////////////////////////////////////////////////////////////////////////

function getChoices(i) {
//Should return above # delimited Structures!
  switch (i) {
    case tagStudeerOpdrachten   : return tagStudeerOpdracht;
    case tagVoorbeeldOpdrachten : return tagVoorbeeldOpdracht;
    case tagOefenOpdrachten     : return tagOefenOpdracht;
    case tagToetsOpdrachten     : return tagToetsOpdracht;
  }
  return "";
}

////////////////////////////////////////////////////////////////////////////////
//Returns true if the tag passed can be deleted in the GUI.
////////////////////////////////////////////////////////////////////////////////

function getDelete(i) {
//Should return above # delimited Structures!
  switch (i) {
    case tagStudeerOpdracht   : return true;
    case tagVoorbeeldOpdracht : return true;
    case tagOefenOpdracht     : return true;
    case tagToetsOpdracht     : return true;
  }
  return false;
}

////////////////////////////////////////////////////////////////////////////////
//Returns true if the tag passed can be previewed in the GUI.
////////////////////////////////////////////////////////////////////////////////

function getPreview(i) {
  switch (i) {
    case tagToets:                  return false;
  }
  return true;
}

////////////////////////////////////////////////////////////////////////////////
//Returns true if the tag is Optional.
////////////////////////////////////////////////////////////////////////////////

function getIsOptional(i) {
  switch (i) {
    case tagBronnen:              return true;
    case tagInstrumenten:         return true;

    case tagStudeeraanwijzingen:  return true;
    case tagIntakeOpdracht:       return true;
    case tagLeerdoelen:           return true;
    case tagZelftoetsOpdracht:    return true;
    case tagCasus:                return true;

    case tagVoorbeeldOpdrachten:  return true;
    case tagVoorbeeldOpdracht:    return true;
    case tagOefenOpdrachten:      return true;
    case tagOefenOpdracht:        return true;
    case tagMetadata:             return true;
  }
  return false;
}

////////////////////////////////////////////////////////////////////////////////
//Returns true if the tag is Optional.
////////////////////////////////////////////////////////////////////////////////

function getOptionalPart(i) {
  switch (i) {
    case tagLeerKern:             return "InleidingPanel"         + crlf +
                                         "AntwoordPanel"          + crlf +
                                         "OutputPanel";

  }
  return "";
}

////////////////////////////////////////////////////////////////////////////////
//Returns a crlf separated list of all tags supported.
////////////////////////////////////////////////////////////////////////////////

function getTags() {
  return tagTheorieTaak        + crlf +
         tagVaardigheidsTaak   + crlf +
         tagIntakeOpdracht     + crlf +
         tagStudeerOpdrachten  + crlf +
         tagStudeerOpdracht    + crlf +
         tagZelftoetsOpdracht  + crlf +
         tagVoorbeeldOpdracht  + crlf +
         tagOefenOpdracht      + crlf +
         tagToetsOpdracht      + crlf +
         tagIntroductie        + crlf +
         tagLeerdoelen         + crlf +
         tagStudeeraanwijzingen+ crlf +
         tagInstrumenten       + crlf +
         tagBronnen            + crlf +
         tagCasus              + crlf +
         tagLeerKern           + crlf +
         tagToets              + crlf +
         tagMetadata;
}

////////////////////////////////////////////////////////////////////////////////
//Returns the name of the focussed control on a certain TFrame Class.
////////////////////////////////////////////////////////////////////////////////

function getFocusPart(t) {
  if (t == "TTitleLastEditorFrame") {
    return "TitleEdit";
  } else if (t == "TXHtmlEditFrame") {
    return "RVEXml";
  } else if (t == "TLeerdoelenSelectorFrame") {
    return "NextGrid1";
  } else if (t == "TStudeeraanwijzingEditorFrame") {
    return "NextGrid1";
  } else if (t == "TBronSelectorFrame") {
    return "NextGrid1";
  } else if (t == "TScenarioEditorFrame") {
    return "NextGrid1";
  } else if (t == "TToetsItemEditorFrame") {
    return "NextGrid1";
  } else if (t == "TMetaDataEditFrame") {
    return "NextGrid1";
  }

  return "";
}

////////////////////////////////////////////////////////////////////////////////
//Returns current date time as UnixDateTime (seconds since Unix Epoch started).
//JScript's Date is msec since the start, Delphi uses seconds since start!
////////////////////////////////////////////////////////////////////////////////

function Now() {
  today = new Date();
  return Math.floor(today / 1000);
}

////////////////////////////////////////////////////////////////////////////////
//Internal XPATH Constants.
////////////////////////////////////////////////////////////////////////////////

var MOODLE                      = '/MOODLE_BACKUP';

var INFO                        = '/MOODLE_BACKUP/INFO';
var DETAILS                     = '/MOODLE_BACKUP/INFO/DETAILS';
var MOD                         = '/MOODLE_BACKUP/INFO/DETAILS/MOD';

var COURSE                      = '/MOODLE_BACKUP/COURSE';
var HEADER                      = '/MOODLE_BACKUP/COURSE/HEADER';
var BLOCKS                      = '/MOODLE_BACKUP/COURSE/BLOCKS';
var QUESTION_CATEGORIES         = '/MOODLE_BACKUP/COURSE/QUESTION_CATEGORIES';
var SECTIONS                    = '/MOODLE_BACKUP/COURSE/SECTIONS';
var GRADEBOOK                   = '/MOODLE_BACKUP/COURSE/GRADEBOOK';
var MODULES                     = '/MOODLE_BACKUP/COURSE/MODULES';

var LEFT                        = 'l';
var RIGHT                       = 'r';

var BIDIGuid                    = '{D6677D1D-15AF-4A7D-A840-C41513DFF7CB}';
var LDGuid                      = '{D6677D1D-15AF-4A7D-A840-C41513DFF7CC}';

var stamp                       = 0;

////////////////////////////////////////////////////////////////////////////////
//Internal XML Helper functions using DOMDocument and XPATH.
////////////////////////////////////////////////////////////////////////////////

//Append <NAME> to XPATH node.
function _appendNP(doc, xpath, name) {
  node = doc.documentElement.selectSingleNode(xpath);

  return node.appendChild(doc.createElement(name));
}

//Append <NAME> & TEXT to XPATH node.
function _appendNATP(doc, xpath, name, text) {
  node = doc.documentElement.selectSingleNode(xpath);

  return node.appendChild(doc.createElement(name)).appendChild(doc.createTextNode(text));
}

//Append MOD to /MOODLE_BACKUP/INFO/DETAILS.
function _appendMOD(doc, name, included, userinfo) {
   node = doc.documentElement.selectSingleNode(DETAILS);

   mod1  = _appendN(node, 'MOD');

   _appendNAT(mod1, 'NAME', name);
   _appendNAT(mod1, 'INCLUDED', new Boolean(included).toString());
   _appendNAT(mod1, 'USERINFO', new Boolean(userinfo).toString());

   return _appendN(mod1, 'INSTANCES');
}

//Append BLOCK to /MOODLE_BACKUP/COURSE/BLOCKS.
function _appendBLOCK(doc, pageid, name, pagetype, position, weight, visible) {
   node = doc.documentElement.selectSingleNode(BLOCKS);

   mod3 = _appendN(node, 'BLOCK');

   _appendNAT(mod3, 'NAME', name);
   _appendNAT(mod3, 'PAGEID',pageid);
   _appendNAT(mod3, 'PAGETYPE', pagetype);
   _appendNAT(mod3, 'POSITION', position);
   _appendNAT(mod3, 'WEIGHT', weight);
   _appendNAT(mod3, 'VISIBLE', visible);

   return _appendN(mod3, 'CONFIGDATA');
}

//Append SECTION to /MOODLE_BACKUP/COURSE/SECTIONS.
function _appendSECTION(doc, sectionid, number, summary, visible) {
   node = doc.documentElement.selectSingleNode(SECTIONS);

   mod4 = _appendN(node, 'SECTION');

   _appendNAT(mod4, 'ID', sectionid);
   _appendNAT(mod4, 'NUMBER',number);
   if (summary=='') {
   //_appendNAT(mod4, 'SUMMARY', 'Geen Samenvatting');
     _appendN(mod4, 'SUMMARY');
   } else {
     _appendNAT(mod4, 'SUMMARY', summary);
   }
   _appendNAT(mod4, 'VISIBLE', visible);

   return _appendN(mod4, 'MODS');
}

//Append INSTANCE to /MOODLE_BACKUP/INFO/DETAILS/MOD/INSTANCES.
function _appendINSTANCEtoMODULE(doc, type, id, name, included, userinfo) {
   node = doc.documentElement.selectSingleNode(MOD+'[NAME="'+type+'"]/INSTANCES');

   mod2 = _appendN(node, 'INSTANCE');

   _appendNAT(mod2, 'ID',id);
   _appendNAT(mod2, 'NAME', name);
   _appendNAT(mod2, 'INCLUDED', new Boolean(included).toString());
   _appendNAT(mod2, 'USERINFO', new Boolean(userinfo).toString());

   return mod2;
}

//Append MOD to /MOODLE_BACKUP/COURSE/SECTIONS/SECTION/MODS
function _appendMODtoSECTION(doc, number, modid, type, instance, added, score, indent, visible, groupmode) {
   node = doc.documentElement.selectSingleNode(SECTIONS+'/SECTION[NUMBER="'+number+'"]/MODS');

   mod5  = _appendN(node, 'MOD');

   _appendNAT(mod5, 'ID', modid);
   _appendNAT(mod5, 'TYPE', type);
   _appendNAT(mod5, 'INSTANCE', instance);
   _appendNAT(mod5, 'ADDED', added);
   _appendNAT(mod5, 'SCORE', score);
   _appendNAT(mod5, 'INDENT', indent);
   _appendNAT(mod5, 'VISIBLE', visible);
   _appendNAT(mod5, 'GROUPMODE', groupmode);

   return mod5;
}

////////////////////////////////////////////////////////////////////////////////
//Internal XML Helper functions using DomNodes.
////////////////////////////////////////////////////////////////////////////////

//Append <NAME> to node.
function _appendN(node, name) {
  return node.appendChild(node.ownerDocument.createElement(name));
}

//Append <NAME> and TEXT to node.
function _appendNAT(node, name, text) {
  return node.appendChild(node.ownerDocument.createElement(name)).appendChild(node.ownerDocument.createTextNode(text));
}

//Append TEXT to node.
function _appendT(node, text) {
  node.appendChild(node.ownerDocument.createTextNode(text));
}

//Append Attribute + Value to node.
function _appendAttribute(node, name, value) {
   att = node.ownerDocument.createAttribute(name);
   att.value = value;
   return node.attributes.setNamedItem(att);
}

//Create a uniqye Stamp based on a GUID. 
function _getStamp() {
   return '_' + stampguid + '+' + (stamp++) + '_';
}

////////////////////////////////////////////////////////////////////////////////
//XML Export function.
////////////////////////////////////////////////////////////////////////////////

var idcounter = 1;              //Generates unique ID's
var now = Now();                //The current Time.
var section = 0;                //The current Section.
var filename = '';              //The exported file's name (compound document).
var resources = '';             //The resources directory used to copy the resources from.
var target = '.\\';             //The base for the course_files directory.
var stampguid = '';             //The stamp's base guid.
var opdracht = -1;              //The current opdracht being processed.

function getExport(fn, res, base, astamp) {

  ////////////////////////////////////////////////////////////////////////////////
  //Instantiate a DOM object at run time.
  ////////////////////////////////////////////////////////////////////////////////

  var dom = new ActiveXObject('msxml2.DOMDocument.3.0');

  dom.async = false;
  dom.resolveExternals = false;
  dom.preserveWhiteSpace = true;

  ////////////////////////////////////////////////////////////////////////////////

  dom.appendChild(dom.createProcessingInstruction("xml", " version='1.0' encoding='utf-8' standalone='yes'"));

  ////////////////////////////////////////////////////////////////////////////////
  //(Re)Set Global Variable.
  ////////////////////////////////////////////////////////////////////////////////

  stampguid     = astamp;
  opdracht      = -1;
  idcounter     = 1;
  section       = 0;
  now           = Now();
  filename      = fn;
  target        = base;
  resources     = res;
  
  ////////////////////////////////////////////////////////////////////////////////
  //Create Basic Structure.
  ////////////////////////////////////////////////////////////////////////////////

  dbg.DebugPrint('------------------------');
  dbg.DebugPrint('Creating Basic Structure...');

  ////////////////////////////////////////////////////////////////////////////////

  mb   = dom.appendChild(dom.createElement('MOODLE_BACKUP'));              //_appendN fails at this point.

  _appendNP(dom, MOODLE, 'INFO');
  _appendNP(dom, MOODLE, 'COURSE');
  _appendNP(dom, COURSE, 'HEADER');
  _appendNP(dom, COURSE, 'BLOCKS');
  _appendNP(dom, COURSE, 'SECTIONS');
//_appendNP(dom, COURSE, 'USERS');
  _appendNP(dom, COURSE, 'QUESTION_CATEGORIES');
//_appendNP(dom, COURSE, 'SCALES');
  _appendNP(dom, COURSE, 'GRADEBOOK');
  _appendNP(dom, COURSE, 'MODULES');

  ////////////////////////////////////////////////////////////////////////////////
  //Add INFO Section.
  ////////////////////////////////////////////////////////////////////////////////

  theorie.Context=theorie.Root;
  _appendNATP(dom, INFO, 'NAME', 'backup-cf101-20060824-1226.zip');             //theorie.Value(theorie.IniMapping, 'ITEM','Titel')
  _appendNATP(dom, INFO, 'MOODLE_VERSION', '2006050506');
  _appendNATP(dom, INFO, 'MOODLE_RELEASE', '1.6 +');
  _appendNATP(dom, INFO, 'BACKUP_VERSION', '2006053000');
  _appendNATP(dom, INFO, 'BACKUP_RELEASE', '1.6');
  _appendNATP(dom, INFO, 'DATE', now);
  _appendNATP(dom, INFO, 'ORIGINAL_WWWROOT', 'http://localhost/moodle');
  _appendNATP(dom, INFO, 'ZIP_METHOD', 'internal');

  ////////////////////////////////////////////////////////////////////////////////
  //Needs to be after above tags.
  ////////////////////////////////////////////////////////////////////////////////

  _appendNP(dom, INFO,   'DETAILS');

  ////////////////////////////////////////////////////////////////////////////////
  //Add HEADER Section..
  ////////////////////////////////////////////////////////////////////////////////

  pid = idcounter++;
  _appendNATP(dom, HEADER, 'ID', pid);
  _appendNP  (dom, HEADER, 'CATEGORY');
  _appendNATP(dom, HEADER + '/CATEGORY', 'ID', idcounter++);
  _appendNATP(dom, HEADER + '/CATEGORY', 'NAME', 'Miscellaneous');              //??
  _appendNP  (dom, HEADER, 'PASSWORD');
  _appendNATP(dom, HEADER, 'FULLNAME', filename);
  _appendNATP(dom, HEADER, 'SHORTNAME', filename);
  _appendNATP(dom, HEADER, 'IDNUMBER', '889');
  _appendNATP(dom, HEADER, 'SUMMARY', 'Beschrijving');
  _appendNATP(dom, HEADER, 'FORMAT', 'iframe');
  _appendNATP(dom, HEADER, 'SHOWGRADES', '1');
  _appendNATP(dom, HEADER, 'NEWSITEMS', '5');
  _appendNATP(dom, HEADER, 'TEACHER', 'Begeleider');
  _appendNATP(dom, HEADER, 'TEACHERS', 'Begeleiders');
  _appendNATP(dom, HEADER, 'STUDENT', 'Student');
  _appendNATP(dom, HEADER, 'STUDENTS', 'Studenten');
  _appendNATP(dom, HEADER, 'GUEST', '0');
  _appendNATP(dom, HEADER, 'STARTDATE', now);
  _appendNATP(dom, HEADER, 'ENROLPERIOD', '0');
  _appendNATP(dom, HEADER, 'NUMSECTIONS', '2');
  _appendNATP(dom, HEADER, 'MAXBYTES', '2097152');
  _appendNATP(dom, HEADER, 'SHOWREPORTS', '0');
  _appendNATP(dom, HEADER, 'GROUPMODE', '0');
  _appendNATP(dom, HEADER, 'GROUPMODEFORCE', '0');
  _appendNP  (dom, HEADER, 'LANG');
  _appendNP  (dom, HEADER, 'THEME');
  _appendNP  (dom, HEADER, 'COST');
  _appendNATP(dom, HEADER, 'CURRENCY', 'USD');
  _appendNATP(dom, HEADER, 'MARKER', '0');
  _appendNATP(dom, HEADER, 'VISIBLE', '1');
  _appendNATP(dom, HEADER, 'HIDDENSECTIONS', '0');
  _appendNATP(dom, HEADER, 'TIMECREATED', now);
  _appendNATP(dom, HEADER, 'TIMEMODIFIED', now);
  _appendNATP(dom, HEADER, 'METACOURSE', '0');

  ////////////////////////////////////////////////////////////////////////////////
  //Add BLOCK Sections
  ////////////////////////////////////////////////////////////////////////////////

  _appendBLOCK(dom, pid, 'course_menu', 'course-view', LEFT, 0, 1);             //ok
  _appendBLOCK(dom, pid, 'online_users', 'course-view', LEFT, 1, 1);            //ok
//_appendBLOCK(dom, pid, 'activity_modules', 'course-view', LEFT, 2, 1);        //ok
//_appendBLOCK(dom, pid, 'news_items', 'course-view', RIGHT, 0, 1);             //ok
//_appendBLOCK(dom, pid, 'course_list', 'course-view', RIGHT, 1, 1);            //ok
//_appendBLOCK(dom, pid, 'calendar_month', 'course-view', RIGHT, 2, 1);         //ok
//_appendBLOCK(dom, pid, 'admin', 'course-view', LEFT, 3, 1);                   //ok
  if (notifications) {
  	_appendBLOCK(dom, pid, 'notification', 'course-view', LEFT, 2, 1);      //ok
  }

  var title = theorie.Value(theorie.IniMapping, 'ITEM','Titel');  //hardcoded theorie
  if (title == '') {
     title = theorie.TypeName;
  }
  _appendSECTION(dom, idcounter++, section, '', 1);

  ////////////////////////////////////////////////////////////////////////////////
  //Add FORUM instance to MODULES.
  ////////////////////////////////////////////////////////////////////////////////

  fid=idcounter++;

  _appendMODtoSECTION(dom, section, idcounter++, 'forum', fid, now, 0, 0, 1, 0);

  node = dom.documentElement.selectSingleNode(DETAILS+'/MOD[NAME="forum"]');
  if (!node) {
    node = _appendMOD(dom, 'forum', true, false);
  }

  _appendINSTANCEtoMODULE(dom, 'forum', fid, 'News forum', true, false);

  mod = _appendNP(dom, MODULES, 'MOD');

  _appendNAT(mod, 'ID', fid);
  _appendNAT(mod, 'MODTYPE', 'forum');
  _appendNAT(mod, 'TYPE', 'news');
  _appendNAT(mod, 'NAME', 'Nieuwsberichten');
  _appendNAT(mod, 'INTRO','Algemeen nieuws');
  _appendNAT(mod, 'OPEN','1');
  _appendNAT(mod, 'ASSESSED','0');
  _appendNAT(mod, 'ASSESSPUBLIC','0');
  _appendNAT(mod, 'ASSESSTIMESTART','0');
  _appendNAT(mod, 'ASSESSTIMEFINISH','0');
  _appendNAT(mod, 'MAXBYTES','0');
  _appendNAT(mod, 'SCALE','0');
  _appendNAT(mod, 'FORCESUBSCRIBE','1');
  _appendNAT(mod, 'TRACKINGTYPE','1');
  _appendNAT(mod, 'RSSTYPE','0');
  _appendNAT(mod, 'RSSARTICLES','0');
  _appendNAT(mod, 'TIMEMODIFIED',now);
  _appendNAT(mod, 'WARNAFTER','0');
  _appendNAT(mod, 'BLOCKAFTER','0');
  _appendNAT(mod, 'BLOCKPERIOD','0');

  ////////////////////////////////////////////////////////////////////////////////
  //Add NOTIFICATIONS instance to MODULES.
  ////////////////////////////////////////////////////////////////////////////////

  if (notifications) {
	nid=idcounter++;

	_appendMODtoSECTION(dom, section, idcounter++, 'notifications', nid, now, 0, 0, 1, 0);

	node = dom.documentElement.selectSingleNode(DETAILS+'/MOD[NAME="notifications"]');
	if (!node) {
	  node = _appendMOD(dom, 'notifications', true, false);
	}

	_appendINSTANCEtoMODULE(dom, 'notifications', nid, 'Notifications', true, false);

	mod = _appendNP(dom, MODULES, 'MOD');

	_appendNAT(mod, 'ID', nid);
	_appendNAT(mod, 'MODTYPE', 'notifications');
	_appendNAT(mod, 'NAME', 'Notificaties');
	_appendN  (mod, 'CONTENT');
	_appendNAT(mod, 'TIMEMODIFIED',now);
  }
  
  ////////////////////////////////////////////////////////////////////////////////
  //Add theorie- & vaardigheidstaak
  ////////////////////////////////////////////////////////////////////////////////

  dbg.DebugPrint('Generating Theorietaak...');
  getWalkNodes(theorie, dom);

  dbg.DebugPrint('Generating Vaardigheidstaak...');
  getWalkNodes(vaardigheid, dom);

  ////////////////////////////////////////////////////////////////////////////////
  //Append DETAILS section.
  ////////////////////////////////////////////////////////////////////////////////

  _appendNATP(dom, DETAILS, 'METACOURSE', 'false');
  _appendNATP(dom, DETAILS, 'USERS', 'course');
  _appendNATP(dom, DETAILS, 'LOGS', 'false');
  _appendNATP(dom, DETAILS, 'USERFILES', 'true');
  _appendNATP(dom, DETAILS, 'COURSEFILES', 'true');
  _appendNATP(dom, DETAILS, 'MESSAGES', 'false');
  _appendNATP(dom, DETAILS, 'BLOCKFORMAT', 'instances');

  ////////////////////////////////////////////////////////////////////////////////
  // Display the content of the object.
  ////////////////////////////////////////////////////////////////////////////////

  dbg.DebugPrint('Exporting "moodle.xml"...');

//Formatted Output  
  var reader = new ActiveXObject("Msxml2.SAXXMLReader.4.0");
  var writer = new ActiveXObject("Msxml2.MXXMLWriter.4.0");
  writer.indent = true;
//writer.standalone = true;
  writer.encoding   = 'UTF-8';
  reader.contentHandler = writer;
  reader.putProperty("http://xml.org/sax/properties/lexical-handler", writer);
//reader.putProperty("http://xml.org/sax/properties/charset", 'utf-8');

  reader.parse(dom);

//return writer.output;

  ////////////////////////////////////////////////////////////////////////////////
  //Dirty fix for msxml ommitting utf-8 encoding all the time from the processing instruction!
  ////////////////////////////////////////////////////////////////////////////////
  var fso = new ActiveXObject("Scripting.FileSystemObject");
  var txt = fso.CreateTextFile(target + 'moodle.xml', true, false);
  
//Dirty Fix to get utf-8 encoding back in...
  var utf = /standalone="yes"/i
  xml = writer.output;
  xml = xml.replace(utf, 'encoding="UTF-8"');  //Moodle style
  xml = theorie.Unicode(xml);
  txt.Write(xml); 

//txt.Write(write.output); 
  txt.Close();

//Unformatted Output  
//dom.save(target + 'moodle.xml'); 

  dbg.DebugPrint('Export completed.');

  return target + 'moodle.xml';
}

////////////////////////////////////////////////////////////////////////////////
//Stack based Routine to walk the Pim Tree.
////////////////////////////////////////////////////////////////////////////////

var
  stack = new Array();

function _recurseNodes(obj, doc) {
  stack.push(obj.Context);

  if (obj.hasChildren) {
    ndx=obj.FirstChild;
    while (ndx!=-1) {
       processNode(obj, doc);
       if (obj.hasChildren) {
         _recurseNodes(obj, doc);
       }
       ndx=obj.NextSibling;
    }
  }
  obj.Context=stack.pop();
}

////////////////////////////////////////////////////////////////////////////////
//Routine to walk the Pim Tree.
////////////////////////////////////////////////////////////////////////////////

function getWalkNodes(obj, doc) {
  obj.Context=obj.Root;

  var fso = new ActiveXObject("Scripting.FileSystemObject");
  if (!fso.FolderExists(target + 'course_files')) {
     fldr = fso.CreateFolder(target + 'course_files');
  }

  //Walk the complete Tree.
  processNode(obj, doc);
  
  _recurseNodes(obj, doc);
}

////////////////////////////////////////////////////////////////////////////////
//Functions to recurse a Tree Object defined in Delphi.
////////////////////////////////////////////////////////////////////////////////

function processNode(obj, dom) {

  switch (obj.Type) {
    case tagTheorieTaak:
    case tagVaardigheidsTaak: {
    
      _renderTaak(obj, dom);

      break;
    }

    case tagStudeerOpdrachten: {
      break;
    }

    case tagIntakeOpdracht:
    case tagStudeerOpdracht:
    case tagZelftoetsOpdracht:
    case tagVoorbeeldOpdracht:
    case tagOefenOpdracht:
    case tagToetsOpdracht: {
      //Cache opdracht type to differentiate tagLeerkern for tagToetsOpdracht.
      opdracht = obj.Type;

      _renderOpdracht(obj, dom);

      break;
    }

    case tagBronnen:
    case tagInstrumenten: {
      if (opdracht==-1) {
        _renderAllResources(obj, dom);
      } else {
        _renderResources(obj, dom);
      }
      break;
    }

    case tagCasus:
    case tagIntroductie: {

     _renderXml(obj, dom);

      break;
    }

    case tagMetadata: {

//veg:No Metadata anymore
//    _renderMetaData(obj, dom);

      break;
    }

    case tagToetsOpgaven: {

      _renderToetsOpgaven(obj, dom);

      break;
    }

    case tagLeerKern: {
      //Differentiate between assigment & workshop (for toetsopdracht).

      if (opdracht != tagToetsOpdracht) {
        _renderLeerkernAsAssigment(obj, dom);
      } else {
        _renderLeerkernAsWorkshop(obj, dom);
      }

      break;
    }


    case tagLeerdoelen: {
      _renderLeerdoelen(obj, dom);

      break;
    }

    case tagStudeeraanwijzingen : {
      _renderStudeeraanwijzingen(obj, dom);

      break;
    }

    case tagCriteria: {
      _renderCriteria(obj, dom);

      break;
    }

    ////////////////////////////////////////////////////////////////////////////////
    //UNRENDERED
    ////////////////////////////////////////////////////////////////////////////////
    case tagVoorbeeldOpdrachten: break;
    case tagOefenOpdrachten: break;
    case tagToetsOpdrachten: break;

    default : {

      dbg.DebugPrint(obj.TypeName + ' [' + (obj.Type) + '] not exported yet.');

      break;
    }
  }
}

////////////////////////////////////////////////////////////////////////////////
//THEORIE & VAARDIGHEIDSTAAK
////////////////////////////////////////////////////////////////////////////////

function _renderTaak(obj, dom) {
  section++;

  var title = obj.Value(obj.IniMapping, 'ITEM','Titel');
  var last = obj.Value(obj.IniMapping, 'ITEM','Studielast');

  if (title=='') {
    title=obj.TypeName;
  }

  if (last!=0) {
    title += ' ('+last+')';
  }

  _appendSECTION(dom, idcounter++, section, '<H2>' + title + '</H2>', 1);
}

////////////////////////////////////////////////////////////////////////////////
//OPDRACHTEN
////////////////////////////////////////////////////////////////////////////////

function _renderOpdracht(obj, dom) {
  lid = idcounter++;

  var title = obj.Value(obj.IniMapping, 'ITEM','Titel');
  var last = obj.Value(obj.IniMapping, 'ITEM','Studielast');

  if (title=='') {
    title=obj.TypeName;
  }

  if (last!=0) {
    title += ' ('+last+')';
  }

  ////////////////////////////////////////////////////////////////////////////////
  //(1)
  node = dom.documentElement.selectSingleNode(DETAILS+'/MOD[NAME="label"]');
  if (!node) {
    _appendMOD(dom, 'label', true, false);
  }

  _appendMODtoSECTION(dom, section, idcounter++, 'label', lid, now, 0, 0, 1, 0);

  ////////////////////////////////////////////////////////////////////////////////
  //(2)
  _appendINSTANCEtoMODULE(dom, 'label', lid, title, true, false);

  ////////////////////////////////////////////////////////////////////////////////
  //(3)
   mod = _appendNP(dom, MODULES, 'MOD');
  _appendNAT(mod, 'ID', lid);
  _appendNAT(mod, 'MODTYPE', 'label');
  _appendNAT(mod, 'NAME', /*obj.TypeName+': ' + */title);
  _appendNAT(mod, 'CONTENT', '<h2>&nbsp;</h2>' + crlf + '<h2>' + title + '</h2>');
  _appendNAT(mod, 'TIMEMODIFIED', now);
}

////////////////////////////////////////////////////////////////////////////////
//BRONNEN & INSTRUMENTEN
////////////////////////////////////////////////////////////////////////////////
/*
[DATA]
ColumnsCount=8
Columns=BIDINoCol;BIDIUsageCol;BIDITitleCol;UrlCol;MediaTypeCol;TypeCol;DescCol;BIDIGuidCol
RowsCount=6
Name=BIDIManager
Row0=1;1;moodlebackup;moodlebackup.xsd;"W3C XML Schema";Bron;;{6AED06CE-2CB2-493C-A6AB-93D69B268EA8}
*/
////////////////////////////////////////////////////////////////////////////////
/*
<html>
 <head>
  <title>Redirect</title>
  <meta http-equiv="Cache-Control" content="no-cache" />
  <meta http-equiv="Pragma" content="no-cache" />
  <meta http-equiv="Expires" content="0" />
  <meta http-equiv="refresh" content="0;URL=http://tweakers.net/nieuws/43856/Borland-komt-met-gratis-versie-ontwikkeltools.html">
 </head>
 <body bgcolor="#ffffff">
Externe Resource (<A HREF="http://www.google.nl/">Google.htm</A>) wordt geladen...
 </body>
</html>
*/
////////////////////////////////////////////////////////////////////////////////

function _renderResources(obj, dom) {
  var firstfile = true;

  //Emit a List of Files to a Directory.

  //Beware of indirection.
  //We need to get a flat list of guids and look them up in the BIDImanager with it's BIDIGuid.

  var ini  = obj.IniMapping;
  var bidi = obj.BiDiMapping;
  var fso = new ActiveXObject("Scripting.FileSystemObject");

  //if we don't do it here we have a clash between a casus and the (file) resources.
  rid=idcounter++;

  //Loop through Bidi Manager content actually used in this node.
  for (i=0; i<obj.RowCount(bidi); i++) {
    guid = obj.Cell(bidi, 'BIDIGuidCol', i);
    if (''+obj.Value(ini, 'DATA', guid) == '1') {
      res = resources + '\\' + obj.Cell(bidi, 'UrlCol', i);
      
      var fso = new ActiveXObject("Scripting.FileSystemObject");
      var fldr;                                                               
      var tf;

      if (firstfile) {
        if (!fso.FolderExists(target + 'course_files')) {
          fldr = fso.CreateFolder(target + 'course_files');
        }

        if (!fso.FolderExists(target + 'course_files\\resources_' + rid)) {
          fldr = fso.CreateFolder(target + 'course_files\\resources_' + rid);
        }

        ////////////////////////////////////////////////////////////////////////////////
        //(1)
        node = dom.documentElement.selectSingleNode(DETAILS+'/MOD[NAME="resource"]');
        if (!node) {
          _appendMOD(dom, 'resource', true, false);
        }

        _appendINSTANCEtoMODULE(dom, 'resource', rid, obj.TypeName, true, false);

        ////////////////////////////////////////////////////////////////////////////////
        //(2)
        _appendMODtoSECTION(dom, section, idcounter++, 'resource', rid, now, 0, 0,1, 0);

        ////////////////////////////////////////////////////////////////////////////////
        //Add resource Module.
        ////////////////////////////////////////////////////////////////////////////////
        //(3)
        //Directory Resource...
        //Actual files in \course_files\sub, dus niet in \moddata\resource
        mod = _appendNP(dom, MODULES, 'MOD');
        _appendNAT(mod, 'ID', rid);
        _appendNAT(mod, 'MODTYPE', 'resource');
        _appendNAT(mod, 'NAME', obj.TypeName);
        _appendNAT(mod, 'TYPE', 'directory');
        _appendNAT(mod, 'REFERENCE', 'resources_' + rid);
        _appendNAT(mod, 'SUMMARY', 'Summary.');
        _appendN  (mod, 'ALLTEXT');
        _appendN  (mod, 'POPUP');
        _appendN  (mod, 'OPTIONS');
        _appendNAT(mod, 'TIMEMODIFIED', now);

        firstfile=false;
      }

      //Create a redirecting html file pointing towards the resource.
      if (fso.FileExists(res)) {
//      fso.CopyFile(res, target + 'course_files\\resources_' + rid + '\\');
        res = obj.Cell(bidi, 'UrlCol', i);
        var txt = fso.CreateTextFile(target + 'course_files\\resources_' + rid + '\\' + obj.Cell(bidi, 'BIDITitleCol', i)+'.htm', true, false);
        txt.WriteLine('<html>');
        txt.WriteLine(' <head>');
        txt.WriteLine('  <title>Redirect</title>');
        txt.WriteLine('  <meta http-equiv="Cache-Control" content="no-cache" />');
        txt.WriteLine('  <meta http-equiv="Pragma" content="no-cache" />');
//      txt.WriteLine('  <meta http-equiv="Expires" content="0" />');
        txt.WriteLine('  <meta http-equiv="refresh" content="0;URL=..\\' + obj.TypeName + '\\' + obj.Cell(bidi, 'UrlCol', i)+'">');
        txt.WriteLine(' </head>');
        txt.WriteLine(' <body bgcolor="#ffffff">');
		
		re = /\\/gi;
		url = '..\\' + obj.TypeName + '\\' + obj.Cell(bidi, 'UrlCol', i);
		url = url.replace(re, "/");
        
        txt.WriteLine('Externe Resource (<A HREF="' + url + '">' + obj.Cell(bidi, 'BIDITitleCol', i) + '</A>) wordt geladen...');
        
        txt.WriteLine(' </body>');
        txt.WriteLine('</html>');
        txt.Close();
      } else {
        var txt = fso.CreateTextFile(target + 'course_files\\resources_' + rid + '\\' + obj.Cell(bidi, 'BIDITitleCol', i)+'.htm', true, false);
        txt.WriteLine('<html>');
        txt.WriteLine(' <head>');
        txt.WriteLine('  <title>Redirect</title>');
        txt.WriteLine('  <meta http-equiv="Cache-Control" content="no-cache" />');
        txt.WriteLine('  <meta http-equiv="Pragma" content="no-cache" />');
//      txt.WriteLine('  <meta http-equiv="Expires" content="0" />');
        txt.WriteLine('  <meta http-equiv="refresh" content="0;URL='+obj.Cell(bidi, 'UrlCol', i)+'">');
        txt.WriteLine(' </head>');
        txt.WriteLine(' <body bgcolor="#ffffff">');
        txt.WriteLine('Externe Resource (<A HREF="' + obj.Cell(bidi, 'UrlCol', i) + '">' + obj.Cell(bidi, 'BIDITitleCol', i) + '</A>) wordt geladen...');
        txt.WriteLine(' </body>');
        txt.WriteLine('</html>');
        txt.Close();
      }
    }
  }
}

////////////////////////////////////////////////////////////////////////////////
//ALL BRONNEN & INSTRUMENTEN
////////////////////////////////////////////////////////////////////////////////
/*
[DATA]
ColumnsCount=8
Columns=BIDINoCol;BIDIUsageCol;BIDITitleCol;UrlCol;MediaTypeCol;TypeCol;DescCol;BIDIGuidCol
RowsCount=6
Name=BIDIManager
Row0=1;1;moodlebackup;moodlebackup.xsd;"W3C XML Schema";Bron;;{6AED06CE-2CB2-493C-A6AB-93D69B268EA8}
*/
////////////////////////////////////////////////////////////////////////////////
/*
<html>
 <head>
  <title>Redirect</title>
  <meta http-equiv="Cache-Control" content="no-cache" />
  <meta http-equiv="Pragma" content="no-cache" />
  <meta http-equiv="Expires" content="0" />
  <meta http-equiv="refresh" content="0;URL=http://tweakers.net/nieuws/43856/Borland-komt-met-gratis-versie-ontwikkeltools.html">
 </head>
 <body bgcolor="#ffffff">
Externe Resource (<A HREF="http://www.google.nl/">Google.htm</A>) wordt geladen...
 </body>
</html>
*/
////////////////////////////////////////////////////////////////////////////////

function _renderAllResources(obj, dom) {
  var firstfile = true;

  //Emit a List of Files to a Directory.

  //Beware of indirection.
  //We need to get a flat list of guids and look them up in the BIDImanager with it's BIDIGuid.

  var bidi = obj.BiDiMapping;
  var fso = new ActiveXObject("Scripting.FileSystemObject");

  //if we don't do it here we have a clash between a casus and the (file) resources.
  rid=idcounter++;

  //Loop through Bidi Manager content.
  for (i=0; i<obj.RowCount(bidi); i++) {
    guid = obj.Cell(bidi, 'BIDIGuidCol', i);
    if ((obj.Type == tagBronnen && obj.Cell(bidi, 'TypeCol', i) == 'Bron') ||
        (obj.Type == tagInstrumenten && obj.Cell(bidi, 'TypeCol', i) == 'Instrument')) {
      res = resources + '\\' + obj.Cell(bidi, 'UrlCol', i);

      var fso = new ActiveXObject("Scripting.FileSystemObject");
      var fldr;
      var tf;

      if (firstfile) {
        //Beware current Directory is used. Better set by program.
        if (!fso.FolderExists(target + 'course_files')) {
          fldr = fso.CreateFolder(target + 'course_files');
        }

        if (!fso.FolderExists(target + 'course_files\\' + obj.TypeName)) {
          fldr = fso.CreateFolder(target + 'course_files\\' + obj.TypeName);
        }

        if (!fso.FolderExists(target + 'course_files\\Hidden')) {
          fldr = fso.CreateFolder(target + 'course_files\\Hidden');
        }

        ////////////////////////////////////////////////////////////////////////////////
        //(1)
        node = dom.documentElement.selectSingleNode(DETAILS+'/MOD[NAME="resource"]');
        if (!node) {
          _appendMOD(dom, 'resource', true, false);
        }

        _appendINSTANCEtoMODULE(dom, 'resource', rid, obj.TypeName, true, false);

        ////////////////////////////////////////////////////////////////////////////////
        //(2)
        _appendMODtoSECTION(dom, 0, idcounter++, 'resource', rid, now, 0, 0,1, 0);

        ////////////////////////////////////////////////////////////////////////////////
        //Add resource Module.
        ////////////////////////////////////////////////////////////////////////////////
        //(3)
        //Directory Resource...
        //Actual files in \course_files\sub, dus niet in \moddata\resource
        mod = _appendNP(dom, MODULES, 'MOD');
        _appendNAT(mod, 'ID', rid);
        _appendNAT(mod, 'MODTYPE', 'resource');
        _appendNAT(mod, 'NAME', obj.TypeName);
        _appendNAT(mod, 'TYPE', 'directory');
        _appendNAT(mod, 'REFERENCE', obj.TypeName);
        _appendNAT(mod, 'SUMMARY', obj.TypeName + ' bij de gehele Taak');
        _appendN  (mod, 'ALLTEXT');
        _appendN  (mod, 'POPUP');
        _appendN  (mod, 'OPTIONS');
        _appendNAT(mod, 'TIMEMODIFIED', now);

        firstfile=false;
      }

      var targetdir = obj.TypeName;
      if (obj.Cell(bidi, 'BIDIUsageCol', i)=="0") {
        targetdir = 'Hidden';
      }

      dbg.DebugPrint("Processing " + obj.TypeName + ": "+obj.Cell(bidi, 'UrlCol', i) + ", Usage: " + obj.Cell(bidi, "BIDIUsageCol", i));
      if (fso.FileExists(res)) {
          //Copy the actual file into the export.    
          dbg.DebugPrint('Copy: "'+res+'" to "'+target + 'course_files\\' + targetdir + '\\');
          fso.CopyFile(res, target + 'course_files\\' + targetdir + '\\');
      } else {
          //Create a redirecting html file pointing towards the resource.
          var txt = fso.CreateTextFile(target + 'course_files\\' + targetdir + '\\' + obj.Cell(bidi, 'BIDITitleCol', i)+'.htm', true, false);
          txt.WriteLine('<html>');
          txt.WriteLine(' <head>');
          txt.WriteLine('  <title>Redirect</title>');
          txt.WriteLine('  <meta http-equiv="Cache-Control" content="no-cache" />');
          txt.WriteLine('  <meta http-equiv="Pragma" content="no-cache" />');
//        txt.WriteLine('  <meta http-equiv="Expires" content="0" />');
          txt.WriteLine('  <meta http-equiv="refresh" content="0;URL='+obj.Cell(bidi, 'UrlCol', i)+'">');
          txt.WriteLine(' </head>');
          txt.WriteLine(' <body bgcolor="#ffffff">');
          re = /\\/gi;
          txt.WriteLine('Externe Resource (<A HREF="' + obj.Cell(bidi, 'UrlCol', i).replace(re, "/") + '">' + obj.Cell(bidi, 'BIDITitleCol', i) + '</A>) wordt geladen...');
          txt.WriteLine(' </body>');
          txt.WriteLine('</html>');
          txt.Close();
      }
    }
  }
}

////////////////////////////////////////////////////////////////////////////////
//CASUS & INTRODUCTIE
////////////////////////////////////////////////////////////////////////////////

function _renderXml(obj, dom) {
  var xml = obj.Xml(obj.RvfMapping, obj.TypeName);

  if (xml=='') {
  //dbg.DebugPrint('Empty XML');

    return
  }

  ////////////////////////////////////////////////////////////////////////////////
  //(1)
  cid=idcounter++;

  node = dom.documentElement.selectSingleNode(DETAILS+'/MOD[NAME="resource"]');
  if (!node) {
    _appendMOD(dom, 'resource', true, false);
  }

  _appendINSTANCEtoMODULE(dom, 'resource', cid, obj.TypeName, true, false);

  ////////////////////////////////////////////////////////////////////////////////
  //(2)
  _appendMODtoSECTION(dom, section, idcounter++, 'resource', cid, now, 0, 0,1, 0);

  ////////////////////////////////////////////////////////////////////////////////
  //Add resource Module.
  ////////////////////////////////////////////////////////////////////////////////
  //(3)

  //Html resource
  mod = _appendNP(dom, MODULES, 'MOD');
  _appendNAT(mod, 'ID', cid);
  _appendNAT(mod, 'MODTYPE', 'resource');
  _appendNAT(mod, 'NAME', obj.TypeName);
  _appendNAT(mod, 'TYPE', 'file');                                              //was 'file'
  _appendNAT(mod, 'REFERENCE', 'resources_' + cid + '/' + obj.TypeName+'.htm'); //was .xhtml
  _appendNAT(mod, 'SUMMARY', obj.TypeName + '.');
//_appendNAT(mod, 'ALLTEXT', obj.Body(xml));
  _appendN  (mod, 'ALLTEXT');
//_appendNAT(mod, 'POPUP', 'resizable=1,scrollbars=1,directories=1,location=1,menubar=1,toolbar=1,status=1,height=450,width=620');
  _appendN  (mod, 'POPUP');
  _appendN  (mod, 'OPTIONS');
  _appendNAT(mod, 'TIMEMODIFIED', now);

  ////////////////////////////////////////////////////////////////////////////////
  //Write physical file
  ////////////////////////////////////////////////////////////////////////////////
  //(4)
  var fso = new ActiveXObject("Scripting.FileSystemObject");
  var fldr;
  var tf;

  //Beware current Directory is used. Better set by program.
  if (!fso.FolderExists(target + 'course_files')) {
    fldr = fso.CreateFolder(target + 'course_files');
  }

  if (!fso.FolderExists(target + 'course_files\\resources_' + cid)) {
    fldr = fso.CreateFolder(target + 'course_files\\resources_' + cid);
  }

  //Emit Single File to a Directory.
  tf = fso.CreateTextFile(target + 'course_files\\resources_' + cid + '\\' + obj.TypeName+'.htm', true, false); //was .xhtml
  tf.Write(xml);
  tf.Close();

  //Move Embedded Files...
  try {
    fso.MoveFile(target + 'temp\\' + filename + '_*.*', target + 'course_files\\resources_' + cid);
  } catch(exception) {
  //Silence
  }
}

////////////////////////////////////////////////////////////////////////////////
//METADATA
////////////////////////////////////////////////////////////////////////////////
/*
[DATA]
ColumnsCount=4
Columns=FieldCol;ValueCol;HintCol;GuidCol
RowsCount=5
Name=NextGrid1
Row0=Author;"Wim van der Vegt";"De <B>naam van de auteur</B>.";{820748F1-101A-4A6C-BEB5-1844F1C6FBD1}
Row1=Date;"16-08-2006 14:04:06";"De <B>datum van laatste wijziging</B>.";{77631019-A89B-4536-90CD-8B0866F0D64F}
Row2=Organisation;;"De <B>organisatie</B> waaraan de auteur verbonden is.";{584854DB-E71D-40B3-87A9-F5C564330343}
Row3=Language;"Dutch (Netherlands)";"De <b>taal</B>.";{DB09B40E-C67E-44A5-8989-3AE5CF599661}
Row4=Keyword;;<B>Sleutelwoorden</B>.;{395933F9-90C0-497F-B927-7A43C43A7348}
*/
////////////////////////////////////////////////////////////////////////////////

function _renderMetaData(obj, dom) {
  var ini = obj.IniMapping;
  var meta = '';
  for (i = 0; i<obj.RowCount(ini); i++ ) {
     if (obj.Cell(ini, 'ValueCol', i)!='') {
        meta = meta + obj.Cell(ini, 'FieldCol', i) + ' = ' + obj.Cell(ini, 'ValueCol', i) + crlf;
     }
  }
  if (meta=='') {
    return;
  }

  ////////////////////////////////////////////////////////////////////////////////
  //(1)
  cid=idcounter++;

  node = dom.documentElement.selectSingleNode(DETAILS+'/MOD[NAME="resource"]');
  if (!node) {
    _appendMOD(dom, 'resource', true, false);
  }

  _appendINSTANCEtoMODULE(dom, 'resource', cid, obj.TypeName, true, false);

  ////////////////////////////////////////////////////////////////////////////////
  //(2)
  _appendMODtoSECTION(dom, section, idcounter++, 'resource', cid, now, 0, 0,1, 0);

  ////////////////////////////////////////////////////////////////////////////////
  //Add resource Module.
        ////////////////////////////////////////////////////////////////////////////////
  //(3)

  //Directory Resource...
  //Actual files in \course_files\sub, dus niet in \moddata\resource
  mod = _appendNP(dom, MODULES, 'MOD');
  _appendNAT(mod, 'ID', cid);
  _appendNAT(mod, 'MODTYPE', 'resource');
  _appendNAT(mod, 'NAME', obj.TypeName);
  _appendNAT(mod, 'TYPE', 'text');
  _appendN  (mod, 'REFERENCE');
  _appendNAT(mod, 'SUMMARY', obj.TypeName + '.');
  _appendNAT(mod, 'ALLTEXT', meta);
//_appendNAT(mod, 'POPUP', 'resizable=1,scrollbars=1,directories=1,location=1,menubar=1,toolbar=1,status=1,height=450,width=620');
  _appendN  (mod, 'POPUP');
  _appendN  (mod, 'OPTIONS');
  _appendNAT(mod, 'TIMEMODIFIED', now);
}

////////////////////////////////////////////////////////////////////////////////
//LEERKERN as Assigment
////////////////////////////////////////////////////////////////////////////////
/*Mapping:
{ED4A8E75-8BF5-409B-A59B-EF4F9C8EA460}.ini=\content\file_037.ini                //Lijst
{A9B5D131-A955-4C03-8C4A-07445F745560}.rvf=\content\file_098.rvf                //Intro
{0CB8495B-1C66-4EBF-BF7D-A333610638E6}.rvf=\content\file_099.rvf                //Opgave
{0CAFD8FD-0D4C-4FE4-9041-62B3ACD65B28}.rvf=\content\file_101.rvf                //Feedback
{1054D45A-EAE6-4BC9-AB05-2B1BA66E811C}.rvf=\content\file_100.rvf                //Model text
{1054D45A-EAE6-4BC9-AB05-2B1BA66E811C}.ini=\content\file_102.ini                //Model filename
*/
////////////////////////////////////////////////////////////////////////////////
/*file_037.ini file:
[DATA]
ColumnsCount=9
Columns=NoCol;UseCol;TitleCol;TypeCol;GuidCol;InstructieGuidCol;VraagGuidCol;ModelGuidCol;OutputGuidCol
RowsCount=1
Name=NextGrid1
Row0=1;True;"Opgave 1";Upload;{82EF87DF-6104-4A4E-A94B-6211651E9240};{A9B5D131-A955-4C03-8C4A-07445F745560};{0CB8495B-1C66-4EBF-BF7D-A333610638E6};{1054D45A-EAE6-4BC9-AB05-2B1BA66E811C};{0CAFD8FD-0D4C-4FE4-9041-62B3ACD65B28}
*/
////////////////////////////////////////////////////////////////////////////////
/*file_102.ini file:
[DATA]
Model=
*/
////////////////////////////////////////////////////////////////////////////////

function _renderLeerkernAsAssigment(obj, dom) {
  ini = obj.IniMapping;

  for (i = 0; i<obj.RowCount(ini); i++) {
    aid = idcounter++;

    var title = obj.Cell(ini, 'TitleCol', i);
    if (title=='') {
      title='Opgave' + obj.Cell(ini, 'NoCol', i);
    }

    irvf=obj.Mapping('.rvf', obj.Cell(ini, 'InstructieGuidCol', i));
    vrvf=obj.Mapping('.rvf', obj.Cell(ini, 'VraagGuidCol', i));
    mrvf=obj.Mapping('.rvf', obj.Cell(ini, 'ModelGuidCol', i));
    mini=obj.Mapping('.ini', obj.Cell(ini, 'ModelGuidCol', i));
    orvf=obj.Mapping('.rvf', obj.Cell(ini, 'OutputGuidCol', i));                

    ////////////////////////////////////////////////////////////////////////////////
    //(1)
    node = dom.documentElement.selectSingleNode(DETAILS+'/MOD[NAME="assignment"]');
    if (!node) {
      _appendMOD(dom, 'assignment', true, true);
    }

    _appendMODtoSECTION(dom, section, idcounter++, 'assignment', aid, now, 0, 0, 1, 0);

    ////////////////////////////////////////////////////////////////////////////////
    //(2)
    _appendINSTANCEtoMODULE(dom, 'assignment', aid, title, true, true);

    ////////////////////////////////////////////////////////////////////////////////
    //(3)
     mod = _appendNP(dom, MODULES, 'MOD');
    _appendNAT(mod, 'ID', aid);
    _appendNAT(mod, 'MODTYPE', 'assignment');
    _appendNAT(mod, 'NAME', title);
    _appendNAT(mod, 'DESCRIPTION', '<h2>Inleiding:</h2><p />' + crlf + obj.body(irvf) + '<hr />' + crlf + '<h2>Opgave:</h2><p />' + crlf + obj.body(vrvf)  + crlf + '<h2>Toelichting:</h2><p />' + crlf + obj.body(orvf));
    _appendNAT(mod, 'FORMAT', '1');
    _appendNAT(mod, 'RESUBMIT', '0');
    _appendNAT(mod, 'PREVENTLATE', '0');
    _appendNAT(mod, 'EMAILTEACHERS', '0');
    _appendNAT(mod, 'TYPE', '0');                                               //Online, offline??
    _appendNAT(mod, 'VAR1', '0');
    _appendNAT(mod, 'VAR2', '0');
    _appendNAT(mod, 'VAR3', '0');
    _appendNAT(mod, 'VAR4', '0');
    _appendNAT(mod, 'VAR5', '0');
    if (obj.Cell(ini, 'TypeCol', i)=='Upload') {
      _appendNAT(mod, 'ASSIGNMENTTYPE', 'uploadreview');
    }
    if (obj.Cell(ini, 'TypeCol', i)=='Open') {
      _appendNAT(mod, 'ASSIGNMENTTYPE', 'uploadreview'); //Alternative????
    }
    _appendNAT(mod, 'MAXBYTES', '2097152');
    _appendNAT(mod, 'TIMEDUE', '0');
    _appendNAT(mod, 'TIMEAVAILABLE', '0');
    _appendNAT(mod, 'GRADE', '0');
    _appendNAT(mod, 'TIMEMODIFIED', now);
    _appendN  (mod, 'SUBMISSIONS');

    //4
    fn =''+ obj.Value(mini, 'DATA', 'Model');
    if (fn != "") {
      dbg.DebugPrint("Processing Model: "+fn);

      var fso = new ActiveXObject("Scripting.FileSystemObject");
      var fldr;
      var tf;

      //Beware current Directory is used. Better set by program.
      if (!fso.FolderExists(target + 'moddata')) {
        fldr = fso.CreateFolder(target + 'moddata');
      }

      if (!fso.FolderExists(target + 'moddata\\assignment')) {
        fldr = fso.CreateFolder(target + 'moddata\\assignment');
      }

      if (!fso.FolderExists(target + 'moddata\\assignment\\' + aid)) {
        fldr = fso.CreateFolder(target + 'moddata\\assignment\\' + aid);
      }

      if (!fso.FolderExists(target + 'moddata\\assignment\\' + aid + '\\responses')) {
        fldr = fso.CreateFolder(target + 'moddata\\assignment\\' + aid + '\\responses');
      }
        
      fso.CopyFile(fn, target + 'moddata\\assignment\\' + aid + '\\responses\\');
    } else {
      dbg.DebugPrint(obj.TypeName);
      dbg.DebugPrint(obj.Cell(ini, 'ModelGuidCol', i));
      dbg.DebugPrint(mrvf);

      var xml = obj.Xml(mrvf, obj.TypeName);

      if (xml!='') {
        ////////////////////////////////////////////////////////////////////////////////
        //Write physical file
        ////////////////////////////////////////////////////////////////////////////////
        var fso = new ActiveXObject("Scripting.FileSystemObject");
        var fldr;
        var tf;

        //Beware current Directory is used. Better set by program.
        if (!fso.FolderExists(target + 'moddata')) {
          fldr = fso.CreateFolder(target + 'moddata');
        }

        if (!fso.FolderExists(target + 'moddata\\assignment')) {
          fldr = fso.CreateFolder(target + 'moddata\\assignment');
        }

        if (!fso.FolderExists(target + 'moddata\\assignment\\' + aid)) {
          fldr = fso.CreateFolder(target + 'moddata\\assignment\\' + aid);
        }

        if (!fso.FolderExists(target + 'moddata\\assignment\\' + aid + '\\responses')) {
          fldr = fso.CreateFolder(target + 'moddata\\assignment\\' + aid + '\\responses');
        }

        //Emit Single File to a Directory.
        tf = fso.CreateTextFile(target + 'moddata\\assignment\\' + aid + '\\responses\\Antwoordmodel.htm', true, false); //was .xhtml
        tf.Write(xml);
        tf.Close();

        dbg.DebugPrint('Generated Model Answer as "' + target + 'moddata\\assignment\\' + aid + '\\responses\\Antwoordmodel.htm' + '"');

        //Move Embedded Files...
        try {
          fso.MoveFile(target + 'temp\\' + filename + '_*.*', target + 'course_files\\resources_' + cid);
        } catch(exception) {
        //Silence
        }
      } else {
        dbg.DebugPrint('Empty Answer Model (no file or text).');
      }
    }
  }
}

////////////////////////////////////////////////////////////////////////////////
//LEERKERN as Workshop
////////////////////////////////////////////////////////////////////////////////
/*
{ED4A8E75-8BF5-409B-A59B-EF4F9C8EA460}.ini=\content\file_037.ini                //Lijst
{A9B5D131-A955-4C03-8C4A-07445F745560}.rvf=\content\file_098.rvf                //Intro
{0CB8495B-1C66-4EBF-BF7D-A333610638E6}.rvf=\content\file_099.rvf                //Opgave
{0CAFD8FD-0D4C-4FE4-9041-62B3ACD65B28}.rvf=\content\file_101.rvf                //Feedback
{1054D45A-EAE6-4BC9-AB05-2B1BA66E811C}.rvf=\content\file_100.rvf                //Model text
{1054D45A-EAE6-4BC9-AB05-2B1BA66E811C}.ini=\content\file_102.ini                //Model filename
*/
////////////////////////////////////////////////////////////////////////////////
/*
[DATA]
ColumnsCount=9
Columns=NoCol;UseCol;TitleCol;TypeCol;GuidCol;InstructieGuidCol;VraagGuidCol;ModelGuidCol;OutputGuidCol
RowsCount=1
Name=NextGrid1
Row0=1;True;"Opgave 1";Upload;{82EF87DF-6104-4A4E-A94B-6211651E9240};{A9B5D131-A955-4C03-8C4A-07445F745560};{0CB8495B-1C66-4EBF-BF7D-A333610638E6};{1054D45A-EAE6-4BC9-AB05-2B1BA66E811C};{0CAFD8FD-0D4C-4FE4-9041-62B3ACD65B28}
*/
////////////////////////////////////////////////////////////////////////////////
/*
[DATA]
Model=
*/

////////////////////////////////////////////////////////////////////////////////

var
  workshopsids = new Array();
  
function _renderLeerkernAsWorkshop(obj, dom) {
  ini = obj.IniMapping;

  for (i = 0; i<obj.RowCount(ini); i++) {
    aid = idcounter++;

    var title = obj.Cell(ini, 'TitleCol', i);
    if (title=='') {
      title='Opgave' + obj.Cell(ini, 'NoCol', i);
    }

	var uploads = 0;
    if (obj.Cell(ini, 'TypeCol', i) == 'Upload') {									//Uploads?
		uploads = 1;
	}	
	
    irvf=obj.Mapping('.rvf', obj.Cell(ini, 'InstructieGuidCol', i));
    vrvf=obj.Mapping('.rvf', obj.Cell(ini, 'VraagGuidCol', i));
    mrvf=obj.Mapping('.rvf', obj.Cell(ini, 'ModelGuidCol', i));
    mini=obj.Mapping('.ini', obj.Cell(ini, 'ModelGuidCol', i));
    orvf=obj.Mapping('.rvf', obj.Cell(ini, 'OutputGuidCol', i));            

    ////////////////////////////////////////////////////////////////////////////////
    //(1)
    node = dom.documentElement.selectSingleNode(DETAILS+'/MOD[NAME="workshop"]');
    if (!node) {
      _appendMOD(dom, 'workshop', true, false);
    }

    _appendMODtoSECTION(dom, section, idcounter++, 'workshop', aid, now, 0, 0, 1, 0);

    ////////////////////////////////////////////////////////////////////////////////
    //(2)
    _appendINSTANCEtoMODULE(dom, 'workshop', aid, title, true, false);

    ////////////////////////////////////////////////////////////////////////////////
    //(3)
    workshopsids.push(aid);

//  dbg.DebugPrint(aid);

     mod = _appendNP(dom, MODULES, 'MOD');
    _appendNAT(mod, 'ID', aid);
    _appendNAT(mod, 'MODTYPE', 'workshop');
    _appendNAT(mod, 'NAME', title);
    _appendNAT(mod, 'DESCRIPTION', '<h2>Inleiding:</h2><p />' + crlf + obj.body(irvf) + '<hr />' + crlf + '<h2>Opgave:</h2><p />' + crlf + obj.body(vrvf) + crlf + '<h2>Toelichting:</h2><p />' + crlf + obj.body(orvf));
    _appendNAT(mod, 'WTYPE', '0');                                              //from editor (no of criteria)
    _appendN  (mod, 'NELEMENTS');                                               //from editor (no of criteria)
    _appendN  (mod, 'NATTACHMENTS');                                            //from editor (aantal submissions expected?)
//  _appendNAT(mod, 'PHASE', '0');                                              //not exported, used to determine if it's a pre v1.5 backup!
    _appendNAT(mod, 'FORMAT', '1');
    _appendNAT(mod, 'GRADINGSTRATEGY', '1');
    _appendNAT(mod, 'RESUBMIT', '0');
    _appendNAT(mod, 'AGREEASSESSMENTS', '0');
    _appendNAT(mod, 'HIDEGRADES', '0');
    _appendNAT(mod, 'ANONYMOUS', '1');
    _appendNAT(mod, 'INCLUDESELF', '0');
    _appendNAT(mod, 'MAXBYTES', '2097152');
    _appendNAT(mod, 'SUBMISSIONSTART', now);									//Was in the past ( new Date('1-1-2006') )!
    _appendNAT(mod, 'ASSESSMENTSTART', now);									//Was in the past ( new Date('1-1-2006') )!
    _appendNAT(mod, 'DEADLINE', now+126230400);                                 //not exported (+4 Years)
    _appendNAT(mod, 'SUBMISSIONEND', now+126230400);                            //+4 Years
    _appendNAT(mod, 'ASSESSMENTEND', now+126230400);                            //+4 Years
    _appendNAT(mod, 'RELEASEGRADES', now);                                 
    _appendNAT(mod, 'GRADE', '10');      
    _appendNAT(mod, 'GRADINGGRADE', '0');
    _appendNAT(mod, 'NTASSESSMENTS', '0');
    _appendNAT(mod, 'ASSESSMENTCOMPS', '2');                                    //Fadir
    _appendNAT(mod, 'NSASSESSMENTS', uploads);
    _appendNAT(mod, 'OVERALLOCATION', '0');                                     
    _appendNAT(mod, 'TIMEMODIFIED', now);
    _appendNAT(mod, 'TEACHERWEIGHT', '0');
    _appendNAT(mod, 'SHOWLEAGUETABLE', '0');
    _appendNAT(mod, 'USEPASSWORD', '0');
    _appendN  (mod, 'PASSWORD');

    _appendN  (mod, 'ELEMENTS');
  }
}


////////////////////////////////////////////////////////////////////////////////
//TOETSOPGAVEN
////////////////////////////////////////////////////////////////////////////////
/*
\content\file_031.ini (start)
[DATA]
ColumnsCount=6
Columns=NoCol;TitleCol;TypeCol;GuidCol;LeerdoelCol;LeerdoelGuidCol
RowsCount=1
Name=NextGrid1
Row0=1;"vraag 1";"Multiple Choice";{24954C16-DE95-43FE-83FE-03249EAFA2BB};;
*/
////////////////////////////////////////////////////////////////////////////////
/*
{24954C16-DE95-43FE-83FE-03249EAFA2BB}=\content\dir_082
{24954C16-DE95-43FE-83FE-03249EAFA2BB}.rvf=\content\dir_082\file_083.rvf (vraag)
{24954C16-DE95-43FE-83FE-03249EAFA2BB}.ini=\content\dir_082\file_084.ini (answers/feedback definition)
{873F5EAC-CAF4-4179-98C1-6DA77F517594}.rvf=\content\dir_082\file_085.rvf (answer   #1)
{A3566017-D4F5-4B2C-A97F-1D6C302FF092}.rvf=\content\dir_082\file_086.rvf (feedback #1)
{1952A634-C039-4BBE-96F0-CB6BFB653B03}.rvf=\content\dir_082\file_087.rvf (answer   #2)
{F78730D7-2BE4-4854-B341-9B4DC8A5687F}.rvf=\content\dir_082\file_088.rvf (feedback #2)
*/
////////////////////////////////////////////////////////////////////////////////
/*
\content\dir_082\file_084.ini (linked to by guid!)
[DATA]
ColumnsCount=5
Columns=AntwoordCol;CorrectCol;ScoreCol;AntwoordGuidCol;FeedbackGuidCol
RowsCount=2
Name=AntwoordGrid
Row0="Antwoord 1";True;0;{873F5EAC-CAF4-4179-98C1-6DA77F517594};{A3566017-D4F5-4B2C-A97F-1D6C302FF092}
Row1="Antwoord 2";False;0;{1952A634-C039-4BBE-96F0-CB6BFB653B03};{F78730D7-2BE4-4854-B341-9B4DC8A5687F}
*/
////////////////////////////////////////////////////////////////////////////////

function _renderToetsOpgaven(obj, dom) {
  var ini  = obj.IniMapping;

  if (obj.RowCount(ini)>0) {

    qsid=idcounter++;

    ////////////////////////////////////////////////////////////////////////////////
    //(1)
    node = dom.documentElement.selectSingleNode(DETAILS+'/MOD[NAME="quiz"]');
    if (!node) {
      _appendMOD(dom, 'quiz', true, false);
    }

    _appendMODtoSECTION(dom, section, idcounter++, 'quiz', qsid, now, 0, 0, 1, 0);

    ////////////////////////////////////////////////////////////////////////////////
    //(2)
    _appendINSTANCEtoMODULE(dom, 'quiz', qsid, obj.TypeName, true, false);

    ////////////////////////////////////////////////////////////////////////////////
    //(3)
     mod = _appendNP(dom, MODULES, 'MOD');
    _appendNAT(mod, 'ID', qsid);
    _appendNAT(mod, 'MODTYPE', 'quiz');
    _appendNAT(mod, 'NAME', obj.TypeName);
    _appendNAT(mod, 'INTRO', '<h2>' + obj.TypeName+ '</h2>');
    _appendNAT(mod, 'TIMEOPEN', '0');
    _appendNAT(mod, 'TIMECLOSE', '0');
    _appendNAT(mod, 'OPTIONFLAGS', '0');
    _appendNAT(mod, 'PENALTYSCHEME', '0');
    _appendNAT(mod, 'ATTEMPTS_NUMBER', '0');
    _appendNAT(mod, 'ATTEMPTONLAST', '0');
    _appendNAT(mod, 'GRADEMETHOD', '1');
    _appendNAT(mod, 'DECIMALPOINTS', '1');
    _appendNAT(mod, 'REVIEW', '62415');                                         //??
    _appendNAT(mod, 'QUESTIONSPERPAGE', '0');
    _appendNAT(mod, 'SHUFFLEQUESTIONS', '0');
    _appendNAT(mod, 'SHUFFLEANSWERS', '1');
    qqq = _appendN(mod, 'QUESTIONS');
    _appendNAT(mod, 'SUMGRADES', '2');                                          //??
    _appendNAT(mod, 'GRADE', '10');
    _appendNAT(mod, 'TIMECREATED', '0');
    _appendNAT(mod, 'TIMEMODIFIED', now);
    _appendNAT(mod, 'TIMELIMIT', '0');
    _appendN  (mod, 'PASSWORD');
    _appendN  (mod, 'SUBNET');
    _appendNAT(mod, 'POPUP', '0');
    _appendNAT(mod, 'DELAY1', '0');
    _appendNAT(mod, 'DELAY2', '0');
    qis = _appendN  (mod, 'QUESTION_INSTANCES');

    qids = '';

    ////////////////////////////////////////////////////////////////////////////////
    //(4) - Append Questions themselves.

    var qc = dom.documentElement.selectSingleNode(QUESTION_CATEGORIES+'/QUESTION_CATEGORY');
    if (!qc) {
      qc = _appendNP(dom, QUESTION_CATEGORIES, 'QUESTION_CATEGORY');
    }

    _appendNAT(qc, 'ID', idcounter++);
    _appendNAT(qc, 'NAME', 'Default');
    _appendNAT(qc, 'INFO', 'The default category for questions.');
    _appendNAT(qc, 'PUBLISH', '0');
    _appendNAT(qc, 'STAMP', _getStamp());                                       
    _appendNAT(qc, 'PARENT', '0');
    _appendNAT(qc, 'SORTORDER', '999');

    //QUESTION_CATEGORIES/QUESTION_CATEGORY/QUESTIONS
    qs = _appendN(qc, 'QUESTIONS');

    for (i=0; i<obj.RowCount(ini); i++) {
      qid = idcounter++;

      guid = obj.Cell(ini, 'GuidCol', i);

      basedir = obj.Mapping('', guid);

      afini = obj.Mapping('.ini', guid, basedir);   //Answers Grid
      afrvf = obj.Mapping('.rvf', guid, basedir);   //Questions

      //QUESTION_CATEGORIES/QUESTION_CATEGORY/QUESTIONS/QUESTION
      q = _appendN(qs, 'QUESTION');
      _appendNAT(q, 'ID', qid);                                                 
      _appendNAT(q, 'PARENT', '0');
      _appendNAT(q, 'NAME', obj.Cell(ini, 'TitleCol', i));
      _appendNAT(q, 'QUESTIONTEXT',obj.body(afrvf));
      _appendNAT(q, 'QUESTIONTEXTFORMAT', '1');
      _appendN  (q, 'IMAGE');
      _appendNAT(q, 'DEFAULTGRADE', '1');
      _appendNAT(q, 'PENALTY', '0.1');
      if (obj.Cell(ini, 'TypeCol', i) == 'Multiple Choice') {
        _appendNAT(q, 'QTYPE', 'multichoice');
      } else if (obj.Cell(ini, 'TypeCol', i) == 'Open') {
        _appendNAT(q, 'QTYPE', 'essay');
      }
      _appendNAT(q, 'LENGTH', '1');
      _appendNAT(q, 'STAMP', _getStamp());
      _appendNAT(q, 'VERSION', _getStamp());                                    
      _appendNAT(q, 'HIDDEN', '0');

      //append question instance to quiz module
      //MODULES/MOD/QUESTION_INSTANCE
      var qi = _appendN(qis,'QUESTION_INSTANCE');
      _appendNAT(qi, 'ID', idcounter++);
      _appendNAT(qi, 'QUESTION', qid);

      _appendNAT(qi, 'GRADE', '1');

      if (qids!='') {
         qids = qids+ ',' + qid;
      } else {
         qids = qid;
      }

      //QUESTION_CATEGORIES/QUESTION_CATEGORY/QUESTIONS/QUESTION/MULTICHOICE
      if (obj.Cell(ini, 'TypeCol', i) == 'Multiple Choice') {
        m = _appendN(q, 'MULTICHOICE');

        _appendNAT(m, 'LAYOUT', '0');

        //Make list of Answer ID's on beforehand.
        lst = '';
        for (j=0; j<obj.RowCount(afini);j++) {
          if (lst!='') {
             lst = lst + ',' + (idcounter + j);
          } else {
             lst = idcounter + j;
          }
        }
        _appendNAT(m, 'ANSWERS', lst);

        //Count number of correct Answers.
        cor = 0;
        for (j=0; j<obj.RowCount(afini);j++) {
          if (obj.Cell(afini, 'CorrectCol', j)=='True') {
            cor++;
          }
        }

        if (cor>1) {
          _appendNAT(m, 'SINGLE', '0');
        } else {
          _appendNAT(m, 'SINGLE', '1');
        }
        _appendNAT(m, 'SHUFFLEANSWERS', '0');

        //QUESTION_CATEGORIES/QUESTION_CATEGORY/QUESTIONS/QUESTION/ANSWERS
        as = _appendN(q, 'ANSWERS')

        for (j=0; j<obj.RowCount(afini);j++) {
          aa = _appendN(as, 'ANSWER');

          _appendNAT(aa, 'ID', idcounter++);

          rvf=obj.Mapping('.rvf', obj.Cell(afini, 'AntwoordGuidCol', j), basedir);
          _appendNAT(aa, 'ANSWER_TEXT', obj.body(rvf));

          _appendNAT(aa, 'FRACTION', obj.Cell(afini, 'ScoreCol', j));

          rvf=obj.Mapping('.rvf', obj.Cell(afini, 'FeedbackGuidCol', j), basedir);
          _appendNAT(aa, 'FEEDBACK', obj.body(rvf));
        }
      } else if (obj.Cell(ini, 'TypeCol', i) == 'Open') {
        as = _appendN(q, 'ANSWERS')

        for (j=0; j<obj.RowCount(afini);j++) {
          aa = _appendN(as, 'ANSWER');

          _appendNAT(aa, 'ID', idcounter++);

          //Ignore answer text as it should be plain text....
          //rvf=obj.Mapping('.rvf', obj.Cell(afini, 'AntwoordGuidCol', j), basedir);
          //_appendNAT(aa, 'ANSWER_TEXT', obj.body(rvf));
          _appendNAT(aa, 'ANSWER_TEXT', '*');

          _appendNAT(aa, 'FRACTION', obj.Cell(afini, 'ScoreCol', j));

          //Although moodle doesn't support it in edit mode, html just works...
          rvf=obj.Mapping('.rvf', obj.Cell(afini, 'FeedbackGuidCol', j), basedir);
          _appendNAT(aa, 'FEEDBACK', obj.body(rvf));
        }
      }
    }

    _appendT(qqq, qids + ',0');                                             
  }
}

////////////////////////////////////////////////////////////////////////////////
//LEERDOELEN
/*
[DATA]
ColumnsCount=4
Columns=NoCol;LDUsageCol;LDTitleCol;LDGuidCol
RowsCount=1
Name=LDManager
Row0=1;1;"leerdoel 1";{3F04D359-CDD1-4501-A6D1-E067E5BC3C4D}
*/
////////////////////////////////////////////////////////////////////////////////
/*
[DATA]
{3F04D359-CDD1-4501-A6D1-E067E5BC3C4D}=1
*/
////////////////////////////////////////////////////////////////////////////////

function _renderLeerdoelen(obj, dom) {
  //Beware of indirection.
  //We need to get a flat list of guids and look them up in the LDmanager with it's LDGuid.

  var ini = obj.IniMapping;
  var ldm = obj.LDMapping;
  var ld  = '';

  //if we don't do it here we have a clash between a casus and the (file) resources.
  rid=idcounter++;

  for (i=0; i<obj.RowCount(ldm); i++) {
    guid = obj.Cell(ldm, 'LDGuidCol', i);
    if (''+obj.Value(ini, 'DATA', guid) == '1') {
      if (obj.Cell(ldm, 'LDTitleCol', i) != '') {
        ld += '<h3>' + obj.Cell(ldm, 'LDTitleCol', i) + '</h3>' + crlf;
        rvf = obj.Mapping('.rvf', obj.Cell(ldm, 'LDGuidCol', i));
        if (obj.Body(rvf)!='') {
          ld +=  obj.Body(rvf) + crlf;
        }


      }
    }
  }

  if (ld != '') {
    ld = '<h2>Leerdoel(en):</h2><p />' + crlf + ld + crlf;
  } else {
    return;
  }

  ////////////////////////////////////////////////////////////////////////////////
  //(1)
  cid=idcounter++;

  node = dom.documentElement.selectSingleNode(DETAILS+'/MOD[NAME="resource"]');
  if (!node) {
    _appendMOD(dom, 'resource', true, false);
  }

  _appendINSTANCEtoMODULE(dom, 'resource', cid, obj.TypeName, true, false);

  ////////////////////////////////////////////////////////////////////////////////
  //(2)
  _appendMODtoSECTION(dom, section, idcounter++, 'resource', cid, now, 0, 0,1, 0);

  ////////////////////////////////////////////////////////////////////////////////
  //Add resource Module.
  ////////////////////////////////////////////////////////////////////////////////
  //(3)

  //Directory Resource...
  //Actual files in \course_files\sub, dus niet in \moddata\resource
  mod = _appendNP(dom, MODULES, 'MOD');
  _appendNAT(mod, 'ID', cid);
  _appendNAT(mod, 'MODTYPE', 'resource');
  _appendNAT(mod, 'NAME', obj.TypeName);
  _appendNAT(mod, 'TYPE', 'text');
  _appendN  (mod, 'REFERENCE');
  _appendNAT(mod, 'SUMMARY', obj.TypeName + '.');
  _appendNAT(mod, 'ALLTEXT', ld);
//_appendNAT(mod, 'POPUP', 'resizable=1,scrollbars=1,directories=1,location=1,menubar=1,toolbar=1,status=1,height=450,width=620');
  _appendN  (mod, 'POPUP');
  _appendN  (mod, 'OPTIONS');
  _appendNAT(mod, 'TIMEMODIFIED', now);
}

////////////////////////////////////////////////////////////////////////////////
//STUDEERAANWIJZINGEN
////////////////////////////////////////////////////////////////////////////////
/*
[DATA]
ColumnsCount=3
Columns=NoCol;TitleCol;GuidCol
RowsCount=2
Name=NextGrid1
Row0=1;"studeeraanwijzing 1a";{98377053-3A82-4305-ACC8-040F57BD8D69}
Row1=2;"studeeraanwijzing 2";{A3F34345-1E5D-4FBF-8F74-5427FFE109E1}
*/
////////////////////////////////////////////////////////////////////////////////

function _renderStudeeraanwijzingen(obj, dom) {
  var ini = obj.IniMapping;
  var aanw = '';

  for (i = 0; i<obj.RowCount(ini); i++ ) {
     if (obj.Cell(ini, 'TitleCol', i)!='') {
        aanw = aanw + '<h3>' + obj.Cell(ini, 'TitleCol', i) + '</h3>' + crlf;
        rvf = obj.Mapping('.rvf', obj.Cell(ini, 'GuidCol', i));
        if (obj.Body(rvf)!='') {
          aanw = aanw + obj.Body(rvf) + crlf;
        }
     }
  }

  if (aanw!='') {
    aanw = '<h2>Studeeraanwijzing(en):</h2><p />' + crlf + aanw + crlf;
  } else {
    return;
  }

  ////////////////////////////////////////////////////////////////////////////////
  //(1)
  cid=idcounter++;

  node = dom.documentElement.selectSingleNode(DETAILS+'/MOD[NAME="resource"]');
  if (!node) {
    _appendMOD(dom, 'resource', true, false);
  }

  _appendINSTANCEtoMODULE(dom, 'resource', cid, obj.TypeName, true, false);

  ////////////////////////////////////////////////////////////////////////////////
  //(2)
  _appendMODtoSECTION(dom, section, idcounter++, 'resource', cid, now, 0, 0,1, 0);

  ////////////////////////////////////////////////////////////////////////////////
  //Add resource Module.
  ////////////////////////////////////////////////////////////////////////////////
  //(3)

  //Directory Resource...
  //Actual files in \course_files\sub, dus niet in \moddata\resource
  mod = _appendNP(dom, MODULES, 'MOD');
  _appendNAT(mod, 'ID', cid);
  _appendNAT(mod, 'MODTYPE', 'resource');
  _appendNAT(mod, 'NAME', obj.TypeName);
  _appendNAT(mod, 'TYPE', 'text');
  _appendN  (mod, 'REFERENCE');
  _appendNAT(mod, 'SUMMARY', obj.TypeName + '.');
  _appendNAT(mod, 'ALLTEXT', aanw);
//_appendNAT(mod, 'POPUP', 'resizable=1,scrollbars=1,directories=1,location=1,menubar=1,toolbar=1,status=1,height=450,width=620');
  _appendN  (mod, 'POPUP');
  _appendN  (mod, 'OPTIONS');
  _appendNAT(mod, 'TIMEMODIFIED', now);
}

////////////////////////////////////////////////////////////////////////////////
//BEOORDELINGSCRITERIA
////////////////////////////////////////////////////////////////////////////////
/*
[DATA]
ColumnsCount=3
Columns=NoCol;ValueCol;GuidCol
RowsCount=3
Name=NextGrid1
Row0=1;erwerw;{A39E7419-251B-4439-A8C3-2577B627AD29}
Row1=2;werwerewrewrew;{F718FBCA-284B-4CDE-AAE3-5CC3C9511513}
Row2=3;qewrewrew11;{C2A8A67B-3CEE-4DBA-B18A-BA1C4367D23F}
*/
function _renderCriteria(obj, dom) {
  while (workshopsids.length>0) {
    var wsid = workshopsids.pop()+'';

    var node = dom.documentElement.selectSingleNode(MODULES+'/MOD[ID='+wsid+'][MODTYPE="workshop"]');
    if (node) {
      ini = obj.IniMapping;

      _appendT(dom.documentElement.selectSingleNode(MODULES+'/MOD[ID='+wsid+'][MODTYPE="workshop"]/NELEMENTS'), obj.RowCount(ini));                   //from editor (no of criteria)

      if (obj.RowCount(ini)>0) {
        _appendT(dom.documentElement.selectSingleNode(MODULES+'/MOD[ID='+wsid+'][MODTYPE="workshop"]/NATTACHMENTS'), '1');                            //from editor (no of criteria)
      } else {                             
        _appendT(dom.documentElement.selectSingleNode(MODULES+'/MOD[ID='+wsid+'][MODTYPE="workshop"]/NATTACHMENTS'), '0');                            //from editor (no of criteria)
      }

      var es = dom.documentElement.selectSingleNode(MODULES+'/MOD[ID='+wsid+'][MODTYPE="workshop"]/ELEMENTS')
      for (i=0; i< obj.RowCount(ini); i++) {
        var e = _appendN(es, 'ELEMENT');

        _appendNAT(e, 'ELEMENTNO', i);
        _appendNAT(e, 'DESCRIPTION', obj.Cell(ini, 'ValueCol', i));
        _appendNAT(e, 'SCALE', '5');
        _appendNAT(e, 'MAXSCORE', '4');
        _appendNAT(e, 'WEIGHT', '11');
        _appendNAT(e, 'STDDEV', '0');
        _appendNAT(e, 'TOTALASSESSMENTS', '0');
      }
    }
  }
}
